package com.example.dakotanews.controller;

import com.example.dakotanews.dto.utils.ApiResponse;
import com.example.dakotanews.dto.LoginDTO;
import com.example.dakotanews.dto.utils.ResponseCode;
import com.example.dakotanews.service.UserService;
import com.example.dakotanews.utils.JwtUtil;
import jakarta.servlet.http.HttpServletRequest;
import jakarta.servlet.http.HttpServletResponse;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.security.web.authentication.logout.SecurityContextLogoutHandler;
import org.springframework.util.StringUtils;
import org.springframework.web.bind.annotation.*;

@RestController
@RequestMapping("/user")
public class UserController {

    private final UserService userService;
    private final JwtUtil jwtUtil;

    // 使用构造函数进行自动装配
    @Autowired
    public UserController(
            UserService userService,
            JwtUtil jwtUtil
    ) {
        this.userService = userService;
        this.jwtUtil = jwtUtil;
    }

    /**
     * @name 用户登录功能接口（暂定）（若实现了手机验证登录的功能接口的话需要改名以区别）
     * @description 前端传递一个包含用户名和密码的请求体，然后进行登录验证
     * @param loginDTO （必需）登录请求体，包含用户名和密码
     * @return 统一响应体
     */
    @PostMapping("/login")
    public ApiResponse<Object> login(@RequestBody LoginDTO loginDTO) {
        String username = loginDTO.getUsername();
        String password = loginDTO.getPassword();

        return userService.loginAuthentication(username, password);
    }

    // deprecated
    @PostMapping("/logout")
    public ApiResponse<Object> logout(HttpServletRequest request, HttpServletResponse response) {
        String token = request.getHeader("Authorization");
        if(!StringUtils.hasText(token)) {
            // 若令牌为空
            return new ApiResponse<>(ResponseCode.UNAUTHORIZED, "Empty Token", "令牌是空的");
        }
        Authentication authentication = SecurityContextHolder.getContext().getAuthentication();
        System.out.println("authentication: " + authentication);
        if(authentication != null) {
            new SecurityContextLogoutHandler().logout(request, response, authentication);
        }
        return new ApiResponse<>(ResponseCode.SUCCESS, "请求成功", "退出登录");
    }

    /**
     * @description 用户关注功能接口
     * @param followedUserId （必选）目标用户的ID
     * @param jwt （必选）解析获得执行操作的用户ID
     * @return 操作处理结果（关注，或是取消关注）
     */
    @GetMapping("/follow")
    public ApiResponse<Object> userFollow(
            @RequestParam Integer followedUserId,
            @RequestHeader(value = "Authorization", required = false)String jwt) {

        Integer userId = jwtUtil.extractUserIdFromJWT(jwt);
        if (userId == null) {
            return new ApiResponse<>(ResponseCode.UNAUTHORIZED, "未授权的请求", "请先登录");
        }

        return userService.userFollow(followedUserId, userId);
    }


    /**
     * @description 获取用户个人基本信息功能接口
     * @param visitedUserId 被访问个人信息的用户ID
     * @param jwt 访问个人信息的用户ID，在此处只是为了获取登录用户与被访问用户的关注情况
     * @return 用户个人信息DTO
     */
    @GetMapping("/getUserInfo")
    public ApiResponse<Object> getUserBasicInfo(
            @RequestParam Integer visitedUserId,
            @RequestHeader(value = "Authorization", required = false)String jwt) {

        Integer userId = jwtUtil.extractUserIdFromJWT(jwt);

        return userService.getUserBasicInfo(visitedUserId, userId);
    }

    /**
     * @description 获取用户个人属性信息功能接口
     * @param visitedUserId 被访问的用户ID
     * @param jwt 同上
     * @return 用户个人信息
     */
    @GetMapping("getPropertyInfo")
    public ApiResponse<Object> getUserPropertyInfo(
            @RequestParam Integer visitedUserId,
            @RequestHeader(value = "Authorization", required = false)String jwt) {

        Integer userId = jwtUtil.extractUserIdFromJWT(jwt);

        if(visitedUserId.equals(userId)) {
            // 若访客用户为自己
            return userService.getSelfPropertyInfo(visitedUserId);
        } else {
            // 若访客用户为其他人
            return userService.getOtherPropertyInfo(visitedUserId);
        }
    }
}